package com.easyj.base.util;

import net.coobird.thumbnailator.Thumbnails;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.multipart.MultipartFile;

import com.easyj.base.exception.HandleImageException;

import java.io.*;
import java.util.Base64;



public class ImageUtil {

	 private static Logger log =  LoggerFactory.getLogger(ImageUtil.class);
    /**
     * 从图片的MultipartFile获取InputStream
     *
     * @param multipartFile MultipartFile
     * @return InputStream
     */
    private static InputStream getImgInputStream(MultipartFile multipartFile) {
        InputStream inputStream;
        try {
            byte[] bytes = multipartFile.getBytes();
            inputStream = new ByteArrayInputStream(bytes);
            return inputStream;
        } catch (IOException e) {
            log.error("ImageUtil.getImgInputStream error:{}", e);
            return null;
        }
    }


    /**
     * 转换图片格式为jpg，保持原尺寸不变，并获取新的InputStream
     *
     * @param imageInputStream InputStream
     * @return InputStream
     */
    public static InputStream formatToJPG(InputStream imageInputStream) {
        InputStream inputStream;
        try {
            OutputStream outputStream = new ByteArrayOutputStream();
            Thumbnails.of(imageInputStream).scale(1f).outputFormat("jpg").toOutputStream(outputStream);
            byte[] buf = ((ByteArrayOutputStream) outputStream).toByteArray();
            inputStream = new ByteArrayInputStream(buf);
            return inputStream;
        } catch (IOException e) {
            log.error("ImageUtil.formatToJPG error:{}", e);
            return null;
        }
    }

    /**
     * 转换图片格式为jpg，保持原尺寸不变，并获取新的InputStream
     *
     * @param multipartFile MultipartFile
     * @return InputStream
     */
    public static InputStream formatToJPG(MultipartFile multipartFile) {
        InputStream imgInputStream = getImgInputStream(multipartFile);

        String filename = multipartFile.getOriginalFilename();
        String suffix = filename.substring(filename.lastIndexOf("."));
        if ("jpg".equals(suffix)) {
            return imgInputStream;
        }
        return formatToJPG(imgInputStream);

    }


    /**
     * 压缩图片文件大小,图片尺寸不变
     *
     * @param imgInputStream InputStream
     * @param quality        图片质量
     * @return InputStream
     */
    public static InputStream compressImg(InputStream imgInputStream, float quality) {
        OutputStream outputStream = new ByteArrayOutputStream();
        InputStream inputStream;
        try {
            if (quality > 1) {
                quality = 1;
            } else if (quality <= 0) {
                quality = 0.5f;
            }
            Thumbnails.of(imgInputStream).scale(1f).outputQuality(quality).outputFormat("png").toOutputStream(outputStream);
            byte[] buf = ((ByteArrayOutputStream) outputStream).toByteArray();
            inputStream = new ByteArrayInputStream(buf);
            return inputStream;
        } catch (IOException e) {
            log.error("ImageUtil.compressImg error:{}", e);
            return null;
        }
    }

    /**
     * 压缩图片文件大小,图片尺寸不变,并转为jpg
     *
     * @param multipartFile MultipartFile
     * @param quality       图片质量
     * @return InputStream
     */
    public static InputStream compressImg2jpg(MultipartFile multipartFile, float quality) {
        InputStream imgInputStream = formatToJPG(multipartFile);
        return compressImg(imgInputStream, quality);
    }



    /**
     * 压缩图片文件大小,图片尺寸不变
     *
     * @param imgInputStream 图片imgInputStream
     * @param quality        图片质量
     * @return base64编码的图片
     * @throws HandleImageException 
     */
    public static String compressImgReturnBase64(InputStream imgInputStream, float quality) throws HandleImageException {
        OutputStream outputStream = new ByteArrayOutputStream();
        try {
            if (quality > 1) {
                quality = 1.0f;
            } else if (quality <= 0) {
                quality = 0.5f;
            }
            Thumbnails.of(imgInputStream).scale(1f).outputQuality(quality).outputFormat("png").toOutputStream(outputStream);
            byte[] buf = ((ByteArrayOutputStream) outputStream).toByteArray();
            return Base64.getEncoder().encodeToString(buf);
        } catch (IOException e) {
            log.error("ImageUtil.compressImg error:{}", e);
            throw new HandleImageException("压缩图片错误！");
        }
    }

    /**
     * 压缩图片文件大小,图片尺寸不变
     *
     * @param multipartFile MultipartFile
     * @param quality       图片质量
     * @return base64编码的图片
     * @throws HandleImageException 
     */
    public static String compressImgReturnBase64(MultipartFile multipartFile, float quality) throws HandleImageException {
        InputStream inputStream = formatToJPG(multipartFile);
        return compressImgReturnBase64(inputStream, quality);
    }

 


    /**
     * 按照指定比例进行缩小和放大
     *
     * @param imgInputStream InputStream
     * @param coefficient    缩放系数,coefficient大于1为放大，小于1且大于0为缩小
     * @return InputStream
     * @throws HandleImageException 
     */
    public static InputStream zoomImg(InputStream imgInputStream, float coefficient) throws HandleImageException {
        OutputStream outputStream = new ByteArrayOutputStream();
        InputStream inputStream;
        try {
            Thumbnails.of(imgInputStream).scale(coefficient).toOutputStream(outputStream);
            byte[] buf = ((ByteArrayOutputStream) outputStream).toByteArray();
            inputStream = new ByteArrayInputStream(buf);
            return inputStream;
        } catch (IOException e) {
            log.error("ImageUtil.zoomImg error:{}", e);
            throw new HandleImageException("缩放图像错误！");
        }

    }

    /**
     * 按照指定比例进行缩小和放大,并转为jpg
     *
     * @param multipartFile MultipartFile
     * @param coefficient   缩放系数,coefficient大于1为放大，小于1且大于0为缩小
     * @return InputStream
     * @throws HandleImageException 
     */
    public static InputStream zoomImg2jpg(MultipartFile multipartFile, float coefficient) throws HandleImageException {
        InputStream imgInputStream = formatToJPG(multipartFile);
        return zoomImg(imgInputStream, coefficient);
    }
    
    /**
    * 按照指定比例进行缩小和放大,并转为jpg
    *
    * @param multipartFile MultipartFile
    * @param coefficient   缩放系数,coefficient大于1为放大，小于1且大于0为缩小
    * @return InputStream
    * @throws HandleImageException 
    */
    public static InputStream zoomImg(MultipartFile multipartFile, float coefficient) throws HandleImageException {
        InputStream imgInputStream = getImgInputStream(multipartFile);
        return zoomImg(imgInputStream, coefficient);
    }

    /**
     * 裁剪图片
     *
     * @param imgInputStream InputStream
     * @param x              x方向
     * @param y              y方向
     * @return InputStream
     */
    public static InputStream cutImg(InputStream imgInputStream, int x, int y) {
        OutputStream outputStream = new ByteArrayOutputStream();
        InputStream inputStream;
        try {
            Thumbnails.of(imgInputStream).size(x, y).keepAspectRatio(false).outputFormat("png").toOutputStream(outputStream);
            byte[] buf = ((ByteArrayOutputStream) outputStream).toByteArray();
            inputStream = new ByteArrayInputStream(buf);
            return inputStream;
        } catch (IOException e) {
            log.error("ImageUtil.cutImg error:{}", e);
            return null;
        }
    }

    /**
     * 裁剪图片
     *
     * @param multipartFile MultipartFile
     * @param x             x方向
     * @param y             y方向
     * @return InputStream
     */
    public static InputStream cutImg(MultipartFile multipartFile, int x, int y) {
        InputStream imgInputStream = formatToJPG(multipartFile);
        return cutImg(imgInputStream, x, y);
    }


}
